package com.rankeiot.core.util;

import com.fasterxml.jackson.databind.JavaType;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.rankeiot.core.Context;
import lombok.SneakyThrows;

import java.io.OutputStream;
import java.util.List;
import java.util.Map;

public class JSONUtil {
    private static ObjectMapper objectMapper;
    public static synchronized ObjectMapper getObjectMapper(){
        if(objectMapper==null){
            try {
                objectMapper = Context.getBean(ObjectMapper.class);
            }catch (NullPointerException ne){
                return new ObjectMapper();
            }
        }
        return objectMapper;
    }
    @SneakyThrows
    public static String toPrettyJSONString(Object data){
        return  getObjectMapper().writerWithDefaultPrettyPrinter().writeValueAsString(data);
    }
    @SneakyThrows
    public static String toJSONString(Object data){
      return  getObjectMapper().writeValueAsString(data);
    }
    @SneakyThrows
    public static void write(OutputStream out, Object data){
        getObjectMapper().writeValue(out,data);
    }
    @SneakyThrows
    public static List parseArray(String data){
        return getObjectMapper().readValue(data,List.class);
    }
    @SneakyThrows
    public static <T> List<T> parseArray(String data,Class<T> itemType){
        return getObjectMapper().readValue(data,getType(List.class,itemType));
    }
    @SneakyThrows
    public static Map parseObject(String data){
        return getObjectMapper().readValue(data,Map.class);
    }
    @SneakyThrows
    public static <T> T parseObject(String data, Class<T> type){
        return getObjectMapper().readValue(data,type);
    }
    @SneakyThrows
    public static <T> T parseObject(String data, JavaType type){
        return getObjectMapper().readValue(data,type);
    }
    public static JavaType getType(Class<?> parametrized, Class<?>... parameterClasses){
        return getObjectMapper().getTypeFactory().constructParametricType(parametrized,parameterClasses);
    }
}
